﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;
using ProdeBackEnd.Model;
using ProdeBackEnd.Controller;
using ProdeBackEnd.DAO;
using ProdeBackEnd.Libs;

namespace ProdeBackEnd
{
    // NOTA: puede usar el comando "Rename" del menú "Refactorizar" para cambiar el nombre de clase "Service1" en el código, en svc y en el archivo de configuración.
    public class Service1 : IService1
    {
        private User userLogged;

        public User login(User user)
        {
            UserService userService = UserService.getUserServiceInstance();
            User userDB = userService.getUserByCode(user.getCode());

            if (userDB.isPassEquals(user))
            {
                userLogged = user;
                return userDB;
            }
            else
            {
                return null;
            }           
        }

        public void logout()
        {
            userLogged = null;
        }

        public List<Tournament> getTournaments()
        {
            try
            {
                TournamenteService tournamenteService = TournamenteService.getTournamenteServiceInstance();
                DateTime now = DateTime.Today;

                String where = "Finish > '" + now.ToString("o") + "'";
                return tournamenteService.getTournamentListFilter(where);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public Tournament saveTournament(Tournament tournament)
        {
            TournamenteService tournamenteService = TournamenteService.getTournamenteServiceInstance();
            Persistencia persistencia = Persistencia.getInstance();
            try
            {
                persistencia.openTransaction();
                tournament = tournamenteService.save(tournament);
                persistencia.commit();
                return tournament;
            }
            catch (BusinessException e)
            {
                persistencia.rolback();
                throw e;
            }
        }

        public List<Team> getTeams(String filter)
        {
            try
            {
                TeamService teamService = TeamService.getTeamServiceInstance();
                DateTime now = DateTime.Today;

                return teamService.getTeamListFilter(filter);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public Team saveTeam(Team team)
        {
            TeamService teamService = TeamService.getTeamServiceInstance();
            Persistencia persistencia = Persistencia.getInstance();
            try
            {
                persistencia.openTransaction();
                team = teamService.save(team);
                persistencia.commit();
                return team;
            }
            catch (BusinessException e)
            {
                persistencia.rolback();
                throw e;
            }
        }

        public List<Match> getMatch(String filter)
        {
            try
            {
                MatchService matchService = MatchService.getMatchServiceInstance();
                return matchService.getMatchListFilter(filter);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public Match saveMatch(Match match)
        {
            MatchService matchService = MatchService.getMatchServiceInstance();
            Persistencia persistencia = Persistencia.getInstance();
            try
            {
                persistencia.openTransaction();
                match = matchService.save(match);
                persistencia.commit();
                return match;
            }
            catch (BusinessException e)
            {
                persistencia.rolback();
                throw e;
            }
        }

        public List<UserResult> getUserResult(String filter)
        {
            try
            {
                UserResultService userResultService = UserResultService.getUserResultServiceInstance();
                return userResultService.getUserResultListFilter(filter);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public List<User> getUserList(String filter)
        {
            try
            {
                UserService userService = UserService.getUserServiceInstance();
                return userService.getUserListFilter(filter);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public List<Tournament> getTournamentByUser(long idUser, String filter)
        {
            try
            {
                UserService userService = UserService.getUserServiceInstance();
                return userService.getTournametesIdByUser(idUser, filter);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public List<User> getUserByTournament(long idTournament, String filter)
        {
            try
            {
                UserService userService = UserService.getUserServiceInstance();
                return userService.getUserIdByTournament(idTournament, filter);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public List<UserPoint> getUserpointsByTournamet(User User)
        {
            List<UserPoint> listUserPoint = new List<UserPoint>();
            try
            {
                UserService userService = UserService.getUserServiceInstance();
                List<Tournament> listTournaments = userService.getTournametesByUser(User.getId(), "");
                foreach (Tournament tournament in listTournaments)
                {
                    List<User> listUsers = userService.getUserByTournament(tournament.getId(), "");
                    foreach (User user in listUsers)
                    {

                        int userPoints = 0;

                        UserResultService userResultService = UserResultService.getUserResultServiceInstance();

                        List<UserResult> usersResults = userResultService.getUserResultByIdUser(user.getId());

                        foreach (UserResult userResult in usersResults)
                        {
                            if (userResult.getMatch().getTournament().getId() == tournament.getId())
                            {
                                userPoints += userResult.getPoints();
                            }
                        }
                        listUserPoint.Add(new UserPoint(user.getName(), tournament.getName(), userPoints));
                    }
                }

            }
            catch (BusinessException e)
            {
                throw e;
            }

            return listUserPoint;
        }

        public void signonUserInTeam(User user, long idTournament)
        {
            try
            {
                UserService userService = UserService.getUserServiceInstance();
                TournamenteService tournamentService = TournamenteService.getTournamenteServiceInstance();
                Tournament tournament = tournamentService.getTournamentById(idTournament);
                if (!userService.isUserInTournament(user.getId(), idTournament))
                {
                    userService.saveUserTournament(user, tournament);
                }
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public List<Match> getMatchMissing(User user)
        {
            try
            {
                List<Match> matchesList = new List<Match>();

                UserService userService = UserService.getUserServiceInstance();
                UserResultService userResultService = UserResultService.getUserResultServiceInstance();
                MatchService matchService = MatchService.getMatchServiceInstance();

                List<Tournament> tournaments = userService.getTournametesByUser(user.getId(), "");
                DateTime now = DateTime.Today;

                String SQL = "";

                foreach (Tournament tournamente in tournaments)
                {
                    if (tournamente.getEnd() > now)
                    {
                        SQL = "idTournament = " + tournamente.getId() + " AND " +
                              "Date > '" + now.ToString("o") + "'" ;
                        matchesList.AddRange(matchService.getMatchListFilter(SQL));
                    }
                }

                matchesList.RemoveAll(delegate(Match match)
                {
                    return userResultService.getUserResultByidUserAndIdMatch(user.getId(), match.getId()) != null;
                });

                return matchesList;
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public void saveUserresult(UserResult userResult)
        {
            try
            {
                UserResultService userResultService = UserResultService.getUserResultServiceInstance();
                if (userResultService.getUserResultByidUserAndIdMatch(userResult.getUser().getId(), userResult.getMatch().getId()) == null)
                {
                    userResultService.save(userResult);
                }
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }

        public Match getMatchById(long idMatch)
        {
            try
            {
                MatchService matchService = MatchService.getMatchServiceInstance();
                return matchService.getMatchById(idMatch);
            }
            catch (BusinessException e)
            {
                throw e;
            }
        }
    }
}
